package org.dromara.speed.controller;

import com.alibaba.fastjson2.JSONObject;
import com.alibaba.fastjson2.JSONWriter;
import jakarta.servlet.http.HttpServletRequest;
import lombok.RequiredArgsConstructor;
import org.dromara.common.core.domain.R;
import org.dromara.common.core.utils.StringUtils;
import org.dromara.common.web.core.BaseController;
import org.dromara.speed.constant.OrderConstants;
import org.dromara.speed.domain.AOrderBo;
import org.dromara.speed.domain.NodePushUpdateBo;
import org.dromara.speed.domain.PayGroupTypeQueryBo;
import org.dromara.speed.utils.RequestUtils;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.http.HttpEntity;
import org.springframework.http.HttpHeaders;
import org.springframework.http.MediaType;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.client.RestTemplate;

import java.util.HashMap;
import java.util.Map;
import java.util.Objects;
import java.util.concurrent.CompletableFuture;

@RequiredArgsConstructor
@RestController
@RequestMapping("/api/system/external")
public class ExternalController extends BaseController {

    @Value("${gatewayDomain}")
    public String gatewayDomain;
    private final RestTemplate restTemplate;
//    private final ExternalServiceClient serviceClient;

    /**
     * 获取支付方式
     */
    @PostMapping("/payType")
    public R<?> payType(@RequestBody PayGroupTypeQueryBo bo, HttpServletRequest request) {
        // 请求转发到网关（带完整路径）
        String url = gatewayDomain + "/system/external/payType";

        // 添加请求头传递
        HttpHeaders headers = new HttpHeaders();
        headers.setContentType(MediaType.APPLICATION_JSON);
//        headers.add("X-Forwarded-For", request.getRemoteAddr());
        headers.add(OrderConstants.secret_key, request.getHeader(OrderConstants.secret_key));
        headers.add(OrderConstants.app_id, request.getHeader(OrderConstants.app_id));
        headers.add(OrderConstants.xt_plugin, request.getHeader(OrderConstants.xt_plugin));

        HttpEntity<PayGroupTypeQueryBo> entity = new HttpEntity<>(bo, headers);

        // 实际转发请求
        return restTemplate.postForObject(url, entity, R.class);
    }

    /**
     * 推送订单
     */
    @PostMapping("/push")
    public R<?> push(@RequestBody AOrderBo bo, HttpServletRequest request) {
        // 请求转发到网关（带完整路径）
        String url = gatewayDomain + "/system/external/push";
        bo.setVersion("node");
        long time = System.currentTimeMillis();
        R<?> r;

        // 添加请求头传递
        Map<String, String> headers = new HashMap<>();
        headers.put(OrderConstants.secret_key, request.getHeader(OrderConstants.secret_key));
        headers.put(OrderConstants.app_id, request.getHeader(OrderConstants.app_id));

//        //请求主服务器，获取请求参数
        String res = new RequestUtils().doPostJson(url, JSONObject.toJSONString(bo, JSONWriter.Feature.WriteMapNullValue), headers);
//        PushOrderResponse response = serviceClient.callService(bo, request.getHeader(OrderConstants.secret_key));
//        String res = response.getParams();

        System.out.println("请求主服务器耗时：" + (System.currentTimeMillis() - time));
        if (StringUtils.isBlank(res)) {
            return R.fail("node push fail");
        }

        //解析返回参数
        try {
            r = JSONObject.parseObject(res, R.class);
        } catch (Exception e) {
            return R.fail("response parse error");
        }
        if (R.isError(r) || !res.contains("nodeParams")) {
            return r;
        }

        JSONObject jsonObject = (JSONObject) r.getData();
        //节点参数
        JSONObject nodeParams = jsonObject.getJSONObject("nodeParams");
        //返回参数
        JSONObject returnParams = jsonObject.getJSONObject("returnParams");
        //内嵌类型
        Integer innerType = jsonObject.getInteger("innerType");

        Long orderId = nodeParams.getLong("orderId");
        String fixedKey = nodeParams.getString("fixedKey");
        Long logId = nodeParams.getLong("logId");
        url = nodeParams.getString("url");
        JSONObject params = nodeParams.getJSONObject("params");

        //获取支付链接
        time = System.currentTimeMillis();
        res = new RequestUtils().doPostJsonByToken(url, params.toJSONString());
        long useTime = System.currentTimeMillis() - time;
        System.out.println("获取支付链接耗时：" + useTime);

        //异步更新订单链接信息
        String finalRes = res;
        CompletableFuture.runAsync(() -> {
            NodePushUpdateBo updateBo = new NodePushUpdateBo(orderId, fixedKey, logId, finalRes, useTime);
            new RequestUtils().doPostJson(gatewayDomain + "/system/external/nodeUpdate", JSONObject.toJSONString(updateBo, JSONWriter.Feature.WriteMapNullValue), headers);
        });

        if (StringUtils.isBlank(res)) {
            return R.fail("Request link null");
        }

        //解析返回参数
        try {
            r = JSONObject.parseObject(res, R.class);
        } catch (Exception e) {
            return R.fail(res);
        }

        if (R.isError(r)) {
            return R.fail(r.getMsg());
        }

        JSONObject data = (JSONObject) r.getData();
        String payUrl = data.getString("url");
        String sessionId = data.getString("session_id");

        returnParams.put("checkoutId", StringUtils.isEmpty(payUrl) ? sessionId : "");
        returnParams.put(Objects.equals(innerType, 3) ? "innerLink" : "link", payUrl);

        return R.ok(returnParams);
    }

}
